package com.tc.shiro.controller;

import com.tc.shiro.model.LoginResParam;
import com.tc.shiro.model.OperatorInfo;
import com.tc.shiro.constants.MerchantWebappConstants;
import com.tc.shiro.exceptions.PortalAuthenticationException;
import com.tc.shiro.service.OperatorService;
import com.tc.shiro.utils.IpUtils;
import com.tc.shiro.vo.LoginReqVo;
import com.tc.shiro.vo.LoginRespVo;
import lombok.extern.slf4j.Slf4j;
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.authc.UsernamePasswordToken;
import org.apache.shiro.subject.Subject;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RestController;

import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

@Slf4j
@RestController
@RequestMapping("/shiro")
public class LoginController extends AbstractController {

    @Autowired
    private OperatorService operatorService;

    @RequestMapping(value = "/login", method = RequestMethod.POST)
    public ResponseEntity<LoginRespVo> login(LoginReqVo loginReqVo, HttpServletRequest request,
                                             HttpServletResponse response) {
        // log.info("login-->入参={}", BeanUtil.objectToLogString(loginReqVo));
        LoginRespVo target = new LoginRespVo();
        target.setRespCode("0000");
        target.setRespMsg("登录成功");
        try {
            Subject subject = SecurityUtils.getSubject();
            String ipAddr = IpUtils.getIpAddr(request);
            log.info("登录者getIpAddr:{},getBrowserIp:{},getRealIp:{}", ipAddr, IpUtils.getBrowserIp(request),getRealIp(request));
            UsernamePasswordToken token = new UsernamePasswordToken(loginReqVo.getLoginName(), loginReqVo.getLoginPwd(), ipAddr);
            // 获取操作员信息
            OperatorInfo info = operatorService.queryOperaterInfo(loginReqVo.getLoginName(), null);
            // 登录
            subject.login(token);
            if (info != null) {
                target.setOperatorType(info.getOperatorType());
                target.setRoleNo(info.getRoleNo());
            }
            // 保存用户信息到session
            setToSession(MerchantWebappConstants.OPERATOR_INFO_SESSION_NAME, info);
            // 生成cookie
            generateCookie(loginReqVo, response);
            // 从session中获取osp登录接口返回的结果
            Object loginRes = getFromSession(MerchantWebappConstants.LOGIN_RES_PARAM);
            if (loginRes != null) {
                LoginResParam loginResParam = (LoginResParam) loginRes;
                target.setRespCode(loginResParam.getRespCode());
                target.setRespMsg(loginResParam.getRespMsg());
            }
        } catch (PortalAuthenticationException e) {
            log.error("{},登录发生PortalAuthenticationException异常,e={}", loginReqVo.getLoginName(), e);
            target.setRespCode(e.getCode());
            target.setRespMsg(e.getMsg());
        } catch (Exception e) {
            log.error("{},登录失败,e={}", loginReqVo.getLoginName(), e);
            target.setRespCode("9999");
            target.setRespMsg("未知异常");
        }
        ResponseEntity<LoginRespVo> responseEntity = new ResponseEntity<LoginRespVo>(target, HttpStatus.OK);
        // log.info("login-->出参={}", BeanUtil.objectToLogString(responseEntity));
        return responseEntity;
    }

    /**
     * 生成cookie
     *
     * @param loginReqVo 登录参数
     * @param response
     */
    private void generateCookie(LoginReqVo loginReqVo, HttpServletResponse response) {
        // 创建记住我Cookie
        Cookie rememberMeCookie = new Cookie(MerchantWebappConstants.REMEMBER_ME_COOKIE_NAME,
                loginReqVo.getLoginName());
        if ("1".equals(loginReqVo.getRememberMe())) {
            rememberMeCookie.setMaxAge(60 * 60 * 24 * 7);
        } else {
            rememberMeCookie.setMaxAge(0);
        }
        rememberMeCookie.setDomain("sh.tc.com");
        rememberMeCookie.setPath("/");
        // 创建登录名Cookie
        Cookie loginNameCookie = new Cookie(MerchantWebappConstants.LOGIN_NAME, loginReqVo.getLoginName());
        loginNameCookie.setDomain("sh.vpal.com");
        loginNameCookie.setPath("/");
        response.addCookie(rememberMeCookie);
        response.addCookie(loginNameCookie);
    }
}
